/**
 * video buffer loader
 * Copyright (c) 2009 cmiscm.com
 * date of final modification : 2009. 11. 20 
*/
package com.cmiscm.videos.stream
{
	import com.cmiscm.videos.events.VideoBufferLoadEvent;
	
	import flash.display.Sprite;
	import flash.events.Event;
	import flash.media.Video;
	import flash.net.NetConnection;
	import flash.net.NetStream;

	public class CMbufferload extends Sprite
	{
		private var _bufferConnection:NetConnection;
		private var _bufferStream:NetStream;
		private var _bufferDuration:Number = 0;
		private var _bufferClient:Object = new Object();			
		private var _bufferVideo:Video;
		
		private var _curPercent:Number = 0;
		
		public function CMbufferload($video:Video)
		{
			super();
			setting($video);
		}
		private function setting($video:Video):void
		{
			_bufferConnection = new NetConnection();
			_bufferConnection.connect(null);			
			_bufferStream = new NetStream(_bufferConnection);
			_bufferClient.onMetaData = onNetStreamMetaDataBuffer;
			_bufferStream.client = _bufferClient;
			_bufferVideo = $video;
			_bufferVideo.attachNetStream(_bufferStream);
		}
		
		/**
		 * get video 
		 */		
		public function get video():Video
		{
			return _bufferVideo;
		}
		
		/**
		 * buffer load 
		 * 
		 */		
		public function bufferLoad($url:String, $cache:Boolean=false):void
		{
			if (_bufferStream == null) {
				throw Error("you must addBufferLoad first - ");
			} else {
				var url:String = addCache($url);
				clear();
				_bufferStream.bufferTime = 5;
				var mov_url:String = $url;
				if ($cache) mov_url = addCache($url);
				_bufferStream.play(mov_url);
				_bufferStream.pause();
				startEngin();
			}
		}
		
		private function addCache($url:String):String
		{
			var mov_url:String = $url;
			if (mov_url.indexOf("?") == -1) {
				mov_url += "?unique="+(new Date()).getTime();
			} else {
				mov_url += "&unique="+(new Date()).getTime();
			}
			return mov_url;
		}
		
		/**
		 * destroy 
		 */		
		public function destroy():void
		{
			clear();
			
			if (_bufferStream != null) {
				_bufferStream = null;
				_bufferConnection.close();
				_bufferConnection = null;
				_bufferVideo = null;
				delete _bufferClient.onMetaData;
				_bufferClient = null;
			}
		}
		
		
		/**
		 * clear 
		 */		
		public function clear():void
		{
			stopEngin();
			
			if (_bufferStream != null) _bufferStream.close();
			if (_bufferVideo != null) _bufferVideo.clear();			
			_bufferDuration = 0;
			_curPercent = 0;
		}
		
		private function startEngin():void
		{
			if (this.hasEventListener(Event.ENTER_FRAME)) {
				return;
			} else {
				this.addEventListener(Event.ENTER_FRAME, onUpdate, false, 0, true);
			}
		}
		private function stopEngin():void
		{
			if (this.hasEventListener(Event.ENTER_FRAME)) this.removeEventListener(Event.ENTER_FRAME, onUpdate);
		}
		private function onUpdate(evt:Event):void
		{
			var bufferPercent:Number;
			if (_bufferStream.bytesTotal > 4) {
				bufferPercent = _bufferStream.bytesLoaded / _bufferStream.bytesTotal;
			} else {
				bufferPercent = 0;
			}
			
			bufferPercent = Number(bufferPercent.toFixed(2));
			if (_curPercent != bufferPercent) {
				_curPercent = bufferPercent;
				this.dispatchEvent(new VideoBufferLoadEvent(VideoBufferLoadEvent.BUFFER_PRECENT, bufferPercent));
			}
			if (bufferPercent == 1) {
				clear();
				this.dispatchEvent(new VideoBufferLoadEvent(VideoBufferLoadEvent.FINISH_BUFFER_LOAD, bufferPercent));				
			}
		}
		
		private function onNetStreamMetaDataBuffer(evt:Object):void
		{
			_bufferDuration = evt.duration;
			this.dispatchEvent(new VideoBufferLoadEvent(VideoBufferLoadEvent.COMPLETE_DURATION, 1, _bufferDuration));
		}
	}
}